package com.example.app.manager.c2;

import android.hardware.camera2.CameraAccessException;
import android.hardware.camera2.CameraCaptureSession;
import android.hardware.camera2.CameraCharacteristics;
import android.hardware.camera2.CameraDevice;
import android.hardware.camera2.CaptureRequest;
import android.hardware.camera2.params.StreamConfigurationMap;
import android.media.MediaRecorder;
import android.os.Build;
import android.os.Handler;
import android.support.annotation.RequiresApi;
import android.util.Size;
import android.view.Surface;

import com.example.app.activity.MLog;
import com.example.app.manager.MediaRecorderManager;

import java.util.ArrayList;
import java.util.List;

//录制视频
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public class CameraRecordVideo {
    private String tag = "CameraRecordVideo";
    private Handler backgroundHandler;

    public CameraRecordVideo setBackgroundHandler(Handler backgroundHandler) {
        this.backgroundHandler = backgroundHandler;
        return this;
    }

    //获取合适的视频大小
    private Size selectVideoSize(Size[] choices, Size previewSize) {
        int videoW = previewSize.getWidth();
        int videoH = previewSize.getHeight();
        Size videoSize = null;
        int px = videoW * videoH;
        double minVideo = Math.min(videoW, videoH);
        double maxVideo = Math.max(videoW, videoH);
        double fixationD = minVideo / maxVideo;
        double difference = -1;
        for (Size size : choices) {
            int w = size.getWidth();
            int h = size.getHeight();
            double min = Math.min(w, h);
            double max = Math.max(w, h);
            double d = min / max;
            MLog.e(tag, "预览大小列表 Width：" + w + " Height:" + h + " d:" + d);
            if (videoSize == null) {
                videoSize = size;
                difference = d;
                continue;
            }
            max = Math.max(fixationD, d);
            min = Math.min(fixationD, d);
            double f = min / max;
            if (f == 1 && difference != 1) {
                videoSize = size;
                difference = 1;
                continue;
            }
            int s = videoSize.getHeight() * videoSize.getWidth();
            if (f == 1 && difference == 1) {
                if (px == (w * h)) {
                    videoSize = size;
                    difference = 1;
                    break;
                }
                if (s < (videoW * videoH)) {
                    videoSize = size;
                    difference = 1;
                }
                continue;
            }
            f = Math.abs(f - d);
            if (difference < 1 && difference > f) {
                videoSize = size;
                difference = f;
                continue;
            }
            if (difference < 1 && difference == f && s < (w * h)) {
                videoSize = size;
                difference = f;
                continue;
            }

        }
        MLog.e(tag, "合适的预览大小 Width：" + videoSize.getWidth() + " Height:" + videoSize.getHeight());
        return videoSize;
    }

    private Size videoSize;

    public void setVideoSzie(CameraCharacteristics characteristics, Size previewSize) {
        StreamConfigurationMap map = characteristics.get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP);
        //获取视频输出的尺寸
        Size[] sizes = map.getOutputSizes(MediaRecorder.class);
        videoSize = selectVideoSize(sizes, previewSize);
    }

    /**
     * 创建会话
     *
     * @param cameraDevice
     * @param previewSurface
     * @return
     * @throws CameraAccessException
     */
    public CaptureRequest.Builder getCaptureRequest(CameraDevice cameraDevice, Surface previewSurface) throws CameraAccessException {
        surfaces = new ArrayList();
        //创建预览需要的CaptureRequest.Builder
        CaptureRequest.Builder previewBuilder = cameraDevice.createCaptureRequest(CameraDevice.TEMPLATE_RECORD);
        previewBuilder.addTarget(previewSurface);
        surfaces.add(previewSurface);
        return previewBuilder;
    }

    private List<Surface> surfaces;

    /**
     * 设置视频录制
     *
     * @param direction       屏幕方向
     * @param characteristics
     * @param cameraDevice
     * @param previewBack
     * @param videoPath
     * @return
     * @throws CameraAccessException
     */
    protected void onRecorderStart(CaptureRequest.Builder previewBuilder, int direction,
                                   CameraCharacteristics characteristics,
                                   CameraDevice cameraDevice,
                                   CameraCaptureSession.StateCallback previewBack,
                                   String videoPath) throws CameraAccessException {
        MediaRecorderManager.getInstance().onInitVideoRecorder();
        //视频配置

        MediaRecorderManager.getInstance().setVideoOutput(videoPath,
                videoSize.getWidth(), videoSize.getHeight());

        //相机角度
        Integer cameraOrientation = characteristics.get(CameraCharacteristics.SENSOR_ORIENTATION);
        MediaRecorderManager.getInstance().setPreviewRotate(direction, cameraOrientation);
        //
        MediaRecorderManager.getInstance().setMediaVideoStart();
        Surface recorderSurface = MediaRecorderManager.getInstance().getSurfaceView();
        previewBuilder.addTarget(recorderSurface);
        surfaces.add(recorderSurface);
        //
        cameraDevice.createCaptureSession(surfaces, previewBack, backgroundHandler);

    }

}
